package com.lekang;

import org.activiti.engine.RepositoryService;
import org.activiti.engine.repository.Deployment;
import org.activiti.engine.repository.ProcessDefinition;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;

import java.util.List;

/**
 * 重新部署入住流程
 * 强制部署新版5步流程：申请入住→入住评估→入住审批→入住配置→签约办理
 * 
 * @author 刘卓
 * @date 2025-01-27
 */
@SpringBootTest
public class RedeployCheckinProcess {
    
    @Autowired
    private RepositoryService repositoryService;
    
    /**
     * 强制重新部署checkin流程
     * 这会创建一个新版本，新流程实例会使用新版本
     */
    @Test
    public void redeployCheckinProcess() {
        System.out.println("==================== 开始重新部署checkin流程 ====================");
        
        // 查看当前部署的流程定义
        List<ProcessDefinition> oldDefinitions = repositoryService.createProcessDefinitionQuery()
                .processDefinitionKey("checkin")
                .orderByProcessDefinitionVersion().desc()
                .list();
        
        System.out.println("当前已部署的checkin流程版本: " + oldDefinitions.size() + " 个");
        for (ProcessDefinition pd : oldDefinitions) {
            System.out.println("  - 版本 " + pd.getVersion() + ": name=" + pd.getName() + 
                             ", deploymentId=" + pd.getDeploymentId());
        }
        
        // 强制重新部署
        System.out.println("\n正在重新部署checkin流程...");
        Deployment deployment = repositoryService.createDeployment()
                .addClasspathResource("bpmn/checkin.bpmn20.xml")
                .name("checkin-new-version-" + System.currentTimeMillis())
                .deploy();
        
        System.out.println("✅ 重新部署成功！");
        System.out.println("新部署ID: " + deployment.getId());
        System.out.println("新部署名称: " + deployment.getName());
        
        // 查看新部署后的流程定义
        List<ProcessDefinition> newDefinitions = repositoryService.createProcessDefinitionQuery()
                .processDefinitionKey("checkin")
                .orderByProcessDefinitionVersion().desc()
                .list();
        
        System.out.println("\n新部署后的checkin流程版本: " + newDefinitions.size() + " 个");
        for (ProcessDefinition pd : newDefinitions) {
            System.out.println("  - 版本 " + pd.getVersion() + ": name=" + pd.getName() + 
                             ", deploymentId=" + pd.getDeploymentId() + 
                             (pd.getVersion() == newDefinitions.get(0).getVersion() ? " ⭐ 最新版本" : ""));
        }
        
        System.out.println("\n==================== 部署完成 ====================");
        System.out.println("⚠️  注意：新发起的入住申请会使用新版本的流程");
        System.out.println("⚠️  已存在的流程实例仍会继续使用旧版本，需要重新发起");
    }
    
    /**
     * 删除所有旧版本的checkin流程部署（危险操作，谨慎使用）
     * 注意：只有在没有运行中的流程实例时才能删除
     */
    @Test
    public void deleteOldDeployments() {
        System.out.println("==================== 删除旧版本流程 ====================");
        
        List<ProcessDefinition> definitions = repositoryService.createProcessDefinitionQuery()
                .processDefinitionKey("checkin")
                .orderByProcessDefinitionVersion().desc()
                .list();
        
        if (definitions.isEmpty()) {
            System.out.println("没有找到checkin流程定义");
            return;
        }
        
        // 保留最新版本，删除其他版本
        ProcessDefinition latest = definitions.get(0);
        System.out.println("保留最新版本 v" + latest.getVersion() + " (部署ID: " + latest.getDeploymentId() + ")");
        
        for (int i = 1; i < definitions.size(); i++) {
            ProcessDefinition old = definitions.get(i);
            try {
                System.out.println("正在删除旧版本 v" + old.getVersion() + " (部署ID: " + old.getDeploymentId() + ")...");
                // cascade=true 会删除相关的流程实例、任务等数据
                repositoryService.deleteDeployment(old.getDeploymentId(), true);
                System.out.println("✅ 删除成功");
            } catch (Exception e) {
                System.out.println("❌ 删除失败: " + e.getMessage());
            }
        }
        
        System.out.println("==================== 清理完成 ====================");
    }
}

